<?php
/**
 * Created by PhpStorm.
 * User: chenjunjie
 * Date: 2020/8/25
 * Time: 4:47 PM
 */
namespace App\Service;

use App\Model\XApiCompany;
use App\Model\XApiUser;
use App\Model\XApiUserCompany;
use App\Model\XAttendanceRecord;
use App\Model\XCompanyRoom;
use App\Model\XCompanyRoomConsumeHistory;
use App\Model\XUserTicket;
use FooRedis;
use Hyperf\Di\Annotation\Inject;
use Hyperf\Redis\Redis;
use Hyperf\Utils\ApplicationContext;
use Psr\Container\ContainerInterface;
use Hyperf\DbConnection\Db;
use Hyperf\Utils\Exception\ParallelExecutionException;
use Hyperf\Utils\Coroutine;
use Hyperf\Utils\Parallel;

class UserService
{

    /**
     * 通过 `@Inject` 注解注入由 `@var` 注解声明的属性类型对象
     *
     * @Inject
     * @var \App\FooRedis
     */
    private $redis;

    public function getFromRedis(){
        return $this->redis->keys("*");
    }

    private function redisSet($queryDate,$method,$companyId,$value,$type='int'){


        if($type == 'array'){
            $value = serialize($value);
        }
        $key = sprintf('task_%s_%s_%s',$method,$companyId,$queryDate);

        return $this->redis->set($key, $value);
    }


    public function companyAttendanceRedisCache($date=null,$type=null){


        if($type == null){
            if($date == 'today'){
                if(date("H") <=12) {
                    $queryDates = [date('Y-m-d'),date("Y-m-d",strtotime("-1 day"))];
                }else{
                    $queryDates = [date('Y-m-d')];
                }
            }else{
                $queryDates = [$date];
            }
        }else{

            $dates = explode('+',$date);
            for ($time = strtotime($dates[0]);$time <= strtotime($dates[1]);$time = $time+86400){

                $queryDates[] = date('Y-m-d',$time);
            }
        }
        $companies = XApiCompany::all();
        $parallel = new Parallel(20);

        foreach ($companies as $company){
            foreach ($queryDates as $date){



                $parallel->add(function () use ($company,$date) {
                    $this->getAttendanceRecord($company->id,$date);
                    return $company->id;
                });

            }
        }
        try{
            $results = $parallel->wait();
            var_dump($results);
        } catch(ParallelExecutionException $e){
            // $e->getResults() 获取协程中的返回值。
            // $e->getThrowables() 获取协程中出现的异常。
        }

    }

    /**
     * @param $companyId
     * @param $queryDate
     */
    public function getAttendanceRecord($companyId,$queryDate){

        $cacheData = [];
        $roles = ['marketing_manager','seller_leader','seller','room_manager'];
        $all = XApiUserCompany::where('company_id',$companyId)
            ->count();
        $cacheData['all'] = $all;
//        $this->redisSet($queryDate,'all',$companyId,$all);

        $companyUser = XApiUserCompany::where('company_id',$companyId)
            ->whereIn('status',[0,1])
            ->count();

//        $this->redisSet($queryDate,'companyUser',$companyId,$companyUser);
        $cacheData['companyUser'] = $companyUser;


        //新版考勤
        $onWork = XAttendanceRecord::where('attendance_day',$queryDate)
            ->where('company_id',$companyId)
            ->whereNotNull('onwork_time')
            ->distinct('user_id')
            ->count('user_id');
//        $this->redisSet($queryDate,'onWork',$companyId,$onWork);
        $cacheData['onWork'] = $onWork;

        $other = $onWork;
        foreach ($roles as $role){
            $count[$role] =  DB::table('x_attendance_record')->where('attendance_day',$queryDate)
                ->where('x_api_role.role_code',$role)
                ->where('x_attendance_record.company_id',$companyId)
                ->whereNotNull('onwork_time')
                ->distinct('x_attendance_record.user_id')
//                ->leftJoin('x_api_user_company', 'x_api_user_company.id', '=', 'x_attendance_record.user_company_id')
                ->leftJoin('x_api_role', 'x_attendance_record.role_id', '=', 'x_api_role.id')
                ->count('user_id');
            $other = $other-$count[$role];

//            $this->redisSet($queryDate,'onWork'.$role,$companyId,$count[$role]);
            $cacheData['onWork'.$role] = $count[$role];
        }

//        $this->redisSet($queryDate,'onWorkOther',$companyId,$other);
        $cacheData['onWorkOther'] = $other;



        $realTime = $this->getRealTime($queryDate);
//        var_dump($realTime);
        $redisData['ticketAllCount'] = XUserTicket::where('company_id',$companyId)
            ->where('add_time','>=',$realTime['startTime'])
            ->where('add_time','<',$realTime['endTime'])
            ->count();

//        $this->redisSet($queryDate,'ticketAllCount',$companyId,$redisData['ticketAllCount']);
        $cacheData['ticketAllCount'] = $redisData['ticketAllCount'];

        $redisData['ticketUsedCount'] = XUserTicket::where('company_id',$companyId)
            ->where('add_time','>=',$realTime['startTime'])
            ->where('add_time','<',$realTime['endTime'])
            ->where('status',1)
            ->count();

//        $this->redisSet($queryDate,'ticketUsedCount',$companyId,$redisData['ticketUsedCount']);
        $cacheData['ticketUsedCount'] = $redisData['ticketUsedCount'];



        $consumeCount = XCompanyRoomConsumeHistory::where('company_id',$companyId)
            ->where('add_time','>=',$realTime['startTime'])
            ->where('add_time','<',$realTime['endTime'])
            ->count();
//        $this->redisSet($queryDate,'consumeCount',$companyId,$consumeCount);
        $cacheData['consumeCount'] = $consumeCount;


        $roomCount = XCompanyRoom::where('company_id',$companyId)
            ->where('status','0')
            ->count();
//        $this->redisSet($queryDate,'roomCount',$companyId,$roomCount);
        $cacheData['roomCount'] = $roomCount;
        $this->redisSet($queryDate,'main',$companyId,json_encode($cacheData,JSON_UNESCAPED_UNICODE));
//        $this->redisSet($queryDate,'main',$companyId,serialize($cacheData));

    }
    /**
     * 获取实时时间
     * @param $queryDate
     * @return array
     */
    public function getRealTime($queryDate){

        $startTime = date('Y-m-d',strtotime($queryDate)).' 12:00:00';
        $endTime = date('Y-m-d',strtotime($queryDate)+86400).' 12:00:00';
        return ['startTime'=>$startTime,'endTime'=>$endTime];
    }
}